home *** CD-ROM | disk | FTP | other *** search
/ FishMarket 1.0 / FishMarket v1.0.iso / fishies / 101-125 / disk_107 / csh / comm1.c < prev    next >
C/C++ Source or Header  |  1992-05-06  |  15KB  |  761 lines

  1. /*
  2.  * COMM1.C
  3.  *
  4.  * Matthew Dillon, August 1986
  5.  *
  6.  * Version 2.07M by Steve Drew 10-Sep-87
  7.  *
  8.  */
  9.  
  10. #include "shell.h"
  11. typedef struct FileInfoBlock FIB;
  12.  
  13. #define DIR_SHORT 0x01
  14. #define DIR_FILES 0x02
  15. #define DIR_DIRS  0x04
  16.  
  17. extern int has_wild;
  18. char cwd[256];
  19.  
  20. /*
  21.     Parse the options specified in sw[]
  22.     Setting a bit for each one found
  23. */
  24. get_opt(sw,count)
  25. char *sw;
  26. int *count;
  27. {
  28.    int l,i = 0, opt = 0;
  29.    char *c,*s;
  30.  
  31.    while((++i < ac) && (av[i][0] == '-')) {
  32.     for (c = av[i]+1; *c ; c++) {
  33.         for(l = 0,s = sw;*s && *s != *c; ++s) ++l;
  34.         if (*s) opt |= (1 << l);
  35.     }
  36.    }
  37.    *count = i;
  38.    return(opt);
  39. }
  40.  
  41. do_sleep()
  42. {
  43.    register int i;
  44.  
  45.    if (ac == 2) {
  46.       i = atoi(av[1]);
  47.       while (i > 0) {
  48.      Delay ((long)100);
  49.      i -= 2;
  50.      if (CHECKBREAK())
  51.         break;
  52.       }
  53.    }
  54.    return (0);
  55. }
  56.  
  57.  
  58. do_number()
  59. {
  60.    return (0);
  61. }
  62.  
  63. do_cat()
  64. {
  65.    FILE *fopen(), *fi;
  66.    int i;
  67.    char buf[256];
  68.  
  69.    if (ac == 1) {
  70.       while (gets(buf)) {
  71.      if (CHECKBREAK()) break;
  72.      puts(buf);
  73.      }
  74.       clearerr(stdin);
  75.       return (0);
  76.    }
  77.  
  78.    for (i = 1; i < ac; ++i) {
  79.       if ((fi = fopen (av[i], "r")) != 0) {
  80.        while (fgets(buf,256,fi)) {
  81.         fputs(buf,stdout);
  82.         fflush(stdout);
  83.         if (CHECKBREAK()) {
  84.            breakreset();
  85.            break;
  86.         }
  87.      }
  88.      fclose (fi);
  89.       } else {
  90.      ierror(av[i], 205);
  91.       }
  92.    }
  93.    return (0);
  94. }
  95.  
  96. do_devinfo()
  97. {
  98.    struct DPTR        *dp;
  99.    struct InfoData    *info;
  100.    int stat,i;
  101.    char *p,*s,*get_pwd(),*index();
  102.  
  103.    if (ac == 1) {
  104.       ++ac;
  105.       av[1] = "";
  106.    }
  107.    for (i=1; i < ac; ++i) {
  108.       if (!(dp = dopen (av[i], &stat)))
  109.      continue;
  110.       info = (struct InfoData *)AllocMem((long)sizeof(struct InfoData), MEMF_PUBLIC);
  111.       if (Info (dp->lock, info)) {
  112.  
  113.      s = get_pwd(dp->lock);
  114.      p = index(s,':');
  115.      *p = '\0';
  116.  
  117.      printf ("Unit:%2ld  Errs:%3ld  Used: %-5ld %3ld%%  Free: %-5ld  Volume: %s\n",
  118.          info->id_UnitNumber,
  119.          info->id_NumSoftErrors,
  120.          info->id_NumBlocksUsed,
  121.          (info->id_NumBlocksUsed * 100)/ info->id_NumBlocks,
  122.          (info->id_NumBlocks - info->id_NumBlocksUsed),
  123.          s);
  124.  
  125.       } else {
  126.          pError (av[i]);
  127.       }
  128.       FreeMem (info,(long) sizeof(*info));
  129.       dclose(dp);
  130.    }
  131.    return(0);
  132. }
  133.  
  134.  
  135.  
  136. /* things shared with display_file */
  137.  
  138. char  lspec[128];
  139. int   filecount, col;
  140. long  bytes, blocks;
  141.  
  142. /*
  143.  * the args passed to do_dir will never be expanded
  144.  */
  145. do_dir()
  146. {
  147.    void display_file();
  148.    int i, options;
  149.  
  150.    col = filecount = 0;
  151.    bytes = blocks = 0L;
  152.    *lspec = '\0';
  153.  
  154.    options  = get_opt("sfd",&i);
  155.  
  156.    if (ac == i) {
  157.       ++ac;
  158.       av[i] = "";
  159.    }
  160.    if (!(options & (DIR_FILES | DIR_DIRS)))  options |= (DIR_FILES | DIR_DIRS);
  161.  
  162.    for (; i < ac; ++i) {
  163.       char **eav;
  164.       int c,eac;
  165.       if (!(eav = expand(av[i], &eac)))
  166.      continue;
  167.       QuickSort(eav, eac);
  168.       for(c=0;c < eac && !breakcheck();++c) display_file(options,eav[c]);
  169.       free_expand (eav);
  170.       if (CHECKBREAK()) break;
  171.    }
  172.    if (col)  printf("\n");
  173.    if (filecount > 1) {
  174.       blocks += filecount;     /* account for dir blocks */
  175.       printf (" %ld Blocks, %ld Bytes used in %d files\n", blocks, bytes, filecount);
  176.    }
  177.    return (0);
  178. }
  179.  
  180. void
  181. display_file(options,filestr)
  182. int options;
  183. char *filestr;
  184. {
  185.    long atol();
  186.    int isadir,slen;
  187.    char sc;
  188.    char *c,*s,*fi;
  189.    struct FileLock *lock;
  190.    char *get_pwd();
  191.    char *strcpy();
  192.    
  193. /*     if current dir different from lspec then
  194.        look for ':' or '/' if found lock it and get_pwd.
  195.        else then use cwd.
  196. */
  197.    for(s = c = filestr; *c; ++c) if (*c == ':' || *c == '/') s = c;
  198.    if (*s == ':') ++s;
  199.    sc = *s;
  200.    *s = '\0';
  201.    c = filestr;
  202.    if (!*c) c = cwd;
  203.    if (strcmp (c, &lspec))  {
  204.       strcpy(lspec, c);
  205.       if (col)      printf("\n");
  206.       if (lock = (struct FileLock *)Lock(c,SHARED_LOCK)) {
  207.      printf ("Directory of %s\n", get_pwd(lock));
  208.      UnLock(lock);
  209.       }
  210.       col = 0;
  211.    }
  212.    *s = sc;
  213.    if (sc == '/') s++;
  214.    slen = strlen(s);
  215.    fi = s + slen + 1;
  216.    isadir = (fi[9] =='D');
  217.  
  218.    if (!(((options & DIR_FILES) && !isadir) ||
  219.      ((options & DIR_DIRS)    && isadir)))
  220.       return;
  221.  
  222.    if (options & DIR_SHORT) {
  223.       if ((col == 3) && slen >18) {
  224.      printf("\n");
  225.      col = 0;
  226.       }
  227.       if (isadir)  {
  228.      printf ("\033[33m");
  229.       }
  230.       if (slen >18) {
  231.      printf(" %-37s",s);
  232.      col += 2;
  233.       }
  234.       else {
  235.      printf(" %-18s",s);
  236.      col++;
  237.       }
  238.       if (col > 3) {
  239.      printf("\n");
  240.      col = 0;
  241.       }
  242.       if (isadir) printf("\033[0m");
  243.    }
  244.    else        /* print full info */
  245.       printf("   %-24s %s",s ,fi);
  246.    fflush(stdout);
  247.    fi[13] = fi[18] = '\0';
  248.    bytes  += atol(fi+7);
  249.    blocks += atol(fi+14);
  250.    filecount++;
  251.    return;
  252. }
  253.  
  254. /*
  255.    converts dos date stamp to a time string of form dd-mmm-yy
  256. */
  257. char *
  258. dates(dss)
  259. struct DateStamp *dss;
  260. {
  261.    register struct tm tm;
  262.    register long time, t;
  263.    register int i;
  264.    static char timestr[40];
  265.    static char months[12][4] = {
  266.     "Jan","Feb","Mar","Apr","May","Jun",
  267.     "Jul","Aug","Sep","Oct","Nov","Dec"
  268.    };
  269.    static char days[12] = {
  270.     31,28,31,30,31,30,31,31,30,31,30,31
  271.    };
  272.    time = dss->ds_Days * 24 * 60 * 60 + dss->ds_Minute * 60 +
  273.                        dss->ds_Tick/TICKS_PER_SECOND;
  274.    tm.tm_sec = time % 60; time /= 60;
  275.    tm.tm_min = time % 60; time /= 60;
  276.    tm.tm_hour= time % 24; time /= 24;
  277.    tm.tm_wday= time %  7;
  278.    tm.tm_year= 78 + (time/(4*365+1)) * 4; time %= 4 * 365 + 1;
  279.    while (time) {
  280.     t = 365;
  281.     if ((tm.tm_year&3) == 0) t++;
  282.     if (time < t) break;
  283.     time -= t;
  284.     tm.tm_year++;
  285.    }
  286.    tm.tm_yday = ++time;
  287.    for (i=0;i<12;i++) {
  288.     t = days[i];
  289.     if (i == 1 && (tm.tm_year&3) == 0) t++;
  290.     if (time <= t) break;
  291.     time -= t;
  292.    }
  293.    tm.tm_mon = i;
  294.    tm.tm_mday = time;
  295.  
  296.    sprintf(timestr,"%02d-%s-%2d %02d:%02d:%02d",tm.tm_mday,
  297.         months[tm.tm_mon],tm.tm_year,
  298.         tm.tm_hour,tm.tm_min,tm.tm_sec);
  299.    timestr[18] = '\n';
  300.    timestr[19] = '\0'; /* protection against bad timestamped files */
  301.    return(timestr);
  302.  
  303. }
  304.  
  305. date()
  306. {
  307.    struct   DateStamp    dss;
  308.    char *dates();
  309.  
  310.    DateStamp(&dss);
  311.    printf("%s",dates(&dss));
  312.    return(0);
  313. }
  314.  
  315. do_quit()
  316. {
  317.    if (Src_stack) {
  318.       Quit = 1;
  319.       return(do_return());
  320.    }
  321.    main_exit (0);
  322. }
  323.  
  324.  
  325. do_echo(str)
  326. char *str;
  327. {
  328.    register char *ptr;
  329.    char nl = 1;
  330.  
  331.    for (ptr = str; *ptr && *ptr != ' '; ++ptr);
  332.    if (*ptr == ' ')
  333.       ++ptr;
  334.    if (av[1] && strcmp (av[1], "-n") == 0) {
  335.       nl = 0;
  336.       ptr += 2;
  337.       if (*ptr == ' ')
  338.      ++ptr;
  339.    }
  340.    printf("%s",ptr);
  341.    fflush(stdout);
  342.    if (nl)
  343.       printf("\n");
  344.    return (0);
  345. }
  346.  
  347. do_source(str)
  348. char *str;
  349. {
  350.    register FILE *fi;
  351.    char buf[256], *s;
  352.  
  353.    if (Src_stack == MAXSRC) {
  354.       ierror(NULL,217);
  355.       return(-1);
  356.    }
  357.    if ((fi = fopen (av[1], "r")) == 0) {
  358.       ierror(av[1], 205);
  359.       return(-1);
  360.    }
  361.    set_var(LEVEL_SET, V_PASSED, next_word(next_word(str)));
  362.    ++H_stack;
  363.    Src_pos[Src_stack] = 0;
  364.    Src_base[Src_stack] = (long)fi;
  365.    ++Src_stack;
  366.    while (fgets (buf, 256, fi)) {
  367.       int len = strlen(buf); 
  368.       buf[len-1] = '\0';
  369.       Src_pos[Src_stack - 1] += len;
  370.       if (Verbose && !forward_goto)
  371.      fprintf(stderr,"%s\n",buf);
  372.       exec_command (buf);
  373.       if (CHECKBREAK())
  374.      break;
  375.    }
  376.    --H_stack;
  377.    --Src_stack;
  378.    if (forward_goto)
  379.       ierror(NULL,501);
  380.    forward_goto = 0;
  381.    unset_level(LEVEL_LABEL + Src_stack);
  382.    unset_var(LEVEL_SET, V_GOTOFWD);
  383.    unset_var(LEVEL_SET, V_PASSED);
  384.    fclose (fi);
  385.    return (0);
  386. }
  387.  
  388. /*
  389.  * return ptr to string that contains full cwd spec.
  390.  */
  391. char *
  392. get_pwd(flock)
  393. struct FileLock *flock;
  394. {
  395.    char *ptr;
  396.    char *name;
  397.    int err=0;
  398.    static char pwdstr[256];
  399.  
  400.    struct FileLock *lock, *newlock;
  401.    FIB *fib;
  402.    int i, len;
  403.  
  404.    lock = (struct FileLock *)DupLock(flock);
  405.          
  406.    fib = (FIB *)AllocMem((long)sizeof(FIB), MEMF_PUBLIC);
  407.    pwdstr[i = 255] = '\0';
  408.  
  409.    while (lock) {
  410.       newlock = (struct FileLock *)ParentDir(lock);
  411.       if (!Examine(lock, fib)) ++err;
  412.       name = fib->fib_FileName;
  413.       if (*name == '\0')        /* HACK TO FIX RAM: DISK BUG */
  414.      name = "RAM";
  415.       len = strlen(name);
  416.       if (newlock) {
  417.      if (i == 255) {
  418.         i -= len;
  419.         bmov(name, pwdstr + i, len);
  420.      } else {
  421.         i -= len + 1;
  422.         bmov(name, pwdstr + i, len);
  423.         pwdstr[i+len] = '/';
  424.      }
  425.       } else {
  426.      i -= len + 1;
  427.      bmov(name, pwdstr + i, len);
  428.      pwdstr[i+len] = ':';
  429.       }
  430.       UnLock(lock);
  431.       lock = newlock;
  432.    }
  433.    FreeMem(fib, (long)sizeof(FIB));
  434.    movmem(pwdstr + i, pwdstr, 256 - i);
  435.    if (err) return(cwd);
  436.    return(pwdstr);
  437. }
  438.  
  439. /*
  440.  * set process cwd name and $_cwd, if str != NULL also print it.
  441.  */
  442. do_pwd(str)
  443. char *str;
  444. {
  445.    char *ptr;
  446.  
  447.    if ((struct FileLock *)Myprocess->pr_CurrentDir == 0)
  448.        attempt_cd(":"); /* if we just booted 0 = root lock */
  449.    strcpy(cwd,get_pwd(Myprocess->pr_CurrentDir,1));
  450.    if (str)
  451.       puts(cwd);
  452.    set_var(LEVEL_SET, V_CWD, cwd);
  453.    /* put the current dir name in our CLI task structure */
  454.    ptr = (char *)((ULONG)((struct CommandLineInterface *)
  455.       BADDR(Myprocess->pr_CLI))->cli_SetName << 2);
  456.    ptr[0] = strlen(cwd);
  457.    movmem(cwd,ptr+1,(int)ptr[0]);
  458.    return(0);
  459. }
  460.  
  461.  
  462. /*
  463.  * CD
  464.  *
  465.  * CD(str, 0)        -do CD operation.
  466.  *
  467.  *    standard operation: breakup path by '/'s and process independantly
  468.  *    x:    -reset cwd base
  469.  *    ..    -remove last cwd element
  470.  *    N        -add N or /N to cwd
  471.  */
  472.  
  473. do_cd(str)
  474. char *str;
  475. {
  476.    char sc, *ptr;
  477.    int err=0;
  478.  
  479.    str = next_word(str);
  480.    if (*str == '\0') {
  481.       puts(cwd);
  482.       return(0);
  483.    }
  484.    str[strlen(str)+1] = '\0';           /* add second \0 on end */
  485.    while (*str) {
  486.       for (ptr = str; *ptr && *ptr != '/' && *ptr != ':'; ++ptr);
  487.       switch (*ptr) {
  488.       case ':':
  489.      sc = ptr[1];
  490.      ptr[1] = '\0';
  491.      err = attempt_cd(str);
  492.      ptr[1] = sc;
  493.      break;
  494.       case '\0':
  495.       case '/':
  496.      *ptr = '\0';
  497.      if (strcmp(str, "..") == 0 || str == ptr)
  498.         str = "/";
  499.      if (*str) err = attempt_cd(str);
  500.      break;
  501.       }
  502.       if (err) break;
  503.       str = ptr + 1;
  504.    }
  505.    do_pwd(NULL);     /* set $_cwd */
  506.    return(err);
  507. }
  508.  
  509. attempt_cd(str)
  510. char *str;
  511. {
  512.    struct FileLock *oldlock, *filelock;
  513.  
  514.    if (filelock = (struct FileLock *)Lock(str, ACCESS_READ)) {
  515.       if (isdir(str)) {
  516.      if (oldlock = (struct FileLock *)CurrentDir(filelock))
  517.         UnLock(oldlock);
  518.      return (0);
  519.       }
  520.       UnLock(filelock);
  521.       ierror(str, 212);
  522.    } else {
  523.       ierror(str, 205);
  524.    }
  525.    return (-1);
  526. }
  527.  
  528. do_mkdir()
  529. {
  530.    register int i;
  531.    register struct FileLock *lock;
  532.  
  533.    for (i = 1; i < ac; ++i) {
  534.       if (lock = (struct FileLock *)Lock(av[i],ACCESS_READ)) {
  535.      ierror(av[i],203);
  536.      UnLock (lock);
  537.      continue;
  538.       }
  539.       if (lock = (struct FileLock *)CreateDir (av[i])) {
  540.      UnLock (lock);
  541.      continue;
  542.       }
  543.       pError (av[i]);
  544.    }
  545.    return (0);
  546. }
  547.  
  548.  
  549. do_mv()
  550. {
  551.    char dest[256];
  552.    register int i;
  553.    char *str;
  554.  
  555.    --ac;
  556.    if (isdir(av[ac])) {
  557.       for (i = 1; i < ac; ++i) {
  558.      str = av[i] + strlen(av[i]) - 1;
  559.      while (str != av[i] && *str != '/' && *str != ':')
  560.         --str;
  561.      if (str != av[i])
  562.         ++str;
  563.      if (*str == 0) {
  564.         ierror(av[i], 508);
  565.         return (-1);
  566.      }
  567.      strcpy(dest, av[ac]);
  568.      if (dest[strlen(dest)-1] != ':')
  569.         strcat(dest, "/");
  570.      strcat(dest, str);
  571.      if (Rename(av[i], dest) == 0)
  572.         break;
  573.       }
  574.       if (i == ac)
  575.      return (1);
  576.    } else {
  577.       i = 1;
  578.       if (ac != 2) {
  579.      ierror("", 507);
  580.      return (-1);
  581.       }
  582.       if (Rename (av[1], av[2]))
  583.      return (0);
  584.    }
  585.    pError (av[i]);
  586.    return (-1);
  587. }
  588.  
  589. rm_file(file)
  590. char *file;
  591. {
  592.       if (has_wild) printf("  %s...",file);
  593.       fflush(stdout);
  594.       if (!DeleteFile(file))
  595.      pError (file);
  596.       else
  597.      if (has_wild) printf("Deleted\n");
  598. }
  599.  
  600. do_rm()
  601. {
  602.    int i, recur;
  603.  
  604.    recur = get_opt("r",&i);
  605.  
  606.    for (; i < ac; ++i) {
  607.       if (CHECKBREAK()) break;
  608.       if (isdir(av[i]) && recur)
  609.      rmdir(av[i]);
  610.       if (!(recur && av[i][strlen(av[i])-1] == ':'))
  611.      rm_file(av[i]);
  612.    }
  613.    return (0);
  614. }
  615.  
  616. rmdir(name)
  617. char *name;
  618. {
  619.    register struct FileLock *lock, *cwd;
  620.    register FIB *fib;
  621.    register char *buf;
  622.  
  623.    buf = (char *)AllocMem(256L, MEMF_PUBLIC);
  624.    fib = (FIB *)AllocMem((long)sizeof(FIB), MEMF_PUBLIC);
  625.  
  626.    if (lock = (struct FileLock *)Lock(name, ACCESS_READ)) {
  627.       cwd = (struct FileLock *) CurrentDir(lock);
  628.       if (Examine(lock, fib)) {
  629.      buf[0] = 0;
  630.      while (ExNext(lock, fib)) {
  631.         if (CHECKBREAK()) break;
  632.         if (isdir(fib->fib_FileName))
  633.            rmdir(fib->fib_FileName);
  634.         if (buf[0]) {
  635.            rm_file(buf);
  636.         }
  637.         strcpy(buf, fib->fib_FileName);
  638.      }
  639.      if (buf[0] && !CHECKBREAK()) {
  640.         rm_file(buf);
  641.      }
  642.       }
  643.       UnLock(CurrentDir(cwd));
  644.    } else {
  645.       pError(name);
  646.    }
  647.    FreeMem(fib, (long)sizeof(FIB));
  648.    FreeMem(buf, 256L);
  649. }
  650.  
  651.  
  652.  
  653. do_history()
  654. {
  655.    register struct HIST *hist;
  656.    register int i = H_tail_base;
  657.    register int len = (av[1]) ? strlen(av[1]) : 0;
  658.  
  659.    for (hist = H_tail; hist; hist = hist->prev) {
  660.       if (len == 0 || strncmp(av[1], hist->line, len) == 0) {
  661.      printf ("%3d ", i);
  662.      puts (hist->line);
  663.       }
  664.       ++i;
  665.       if (CHECKBREAK())
  666.      break;
  667.    }
  668.    return (0);
  669. }
  670.  
  671. do_mem()
  672. {
  673.    long cfree, ffree;
  674.    extern long AvailMem();
  675.  
  676.    Forbid();
  677.    cfree = AvailMem (MEMF_CHIP);
  678.    ffree = AvailMem (MEMF_FAST);
  679.    Permit();
  680.  
  681.    if (ffree)        {
  682.    printf ("FAST memory: %ld\n", ffree);
  683.    printf ("CHIP memory: %ld\n", cfree);
  684.    }
  685.    printf ("Total  Free: %ld\n", cfree + ffree);
  686.    return(0);
  687. }
  688.  
  689. /*
  690.  * foreach var_name  ( str str str str... str ) commands
  691.  * spacing is important (unfortunately)
  692.  *
  693.  * ac=0       1 2 3 4 5 6 7
  694.  * foreach i ( a b c ) echo $i
  695.  * foreach i ( *.c )   "echo -n "file ->";echo $i"
  696.  */
  697.  
  698. do_foreach()
  699. {
  700.    register int i, cstart, cend, old;
  701.    register char *cstr, *vname, *ptr, *scr;
  702.    char **fav;
  703.    
  704.    cstart = i = (*av[2] == '(') ? 3 : 2;
  705.    while (i < ac) {
  706.       if (*av[i] == ')')
  707.      break;
  708.       ++i;
  709.    }
  710.    if (i == ac) {
  711.       fprintf (stderr,"')' expected\n");
  712.       return (-1);
  713.    }
  714.    ++H_stack;
  715.    cend = i;
  716.    
  717.    vname = strcpy(malloc(strlen(av[1])+1), av[1]);
  718.    fav = (char **)malloc(sizeof(char *) * (ac));
  719.    cstr = compile_av (av, cend + 1, ac, ' ');
  720.    
  721.    for (i = cstart; i < cend; ++i) {
  722.        fav[i] = av[i];
  723.    }
  724.       
  725.    for (i = cstart; i < cend; ++i) {
  726.       set_var (LEVEL_SET, vname, fav[i]);
  727.       if (CHECKBREAK())
  728.          break;
  729.       exec_command (cstr);
  730.    }        
  731.    --H_stack;
  732.    free (fav);
  733.    free (cstr);
  734.    unset_var (LEVEL_SET, vname);
  735.    free (vname);
  736.    return (0);
  737. }
  738.  
  739. do_forever(str)
  740. char *str;
  741. {
  742.    int rcode = 0;
  743.    char *ptr = next_word(str);
  744.  
  745.    ++H_stack;
  746.    for (;;) {
  747.       if (CHECKBREAK()) {
  748.      rcode = 20;
  749.      break;
  750.       }
  751.       if (exec_command (ptr) < 0) {
  752.      str = get_var(LEVEL_SET, V_LASTERR);
  753.      rcode = (str) ? atoi(str) : 20;
  754.      break;
  755.       }
  756.    }
  757.    --H_stack;
  758.    return (rcode);
  759. }
  760.  
  761.